package com.lzy.business.facade;

import com.alibaba.fastjson.JSON;
import com.lzy.base.apis.SysUserRoleServiceApi;
import com.lzy.base.dtos.SysUserRoleDto;
import com.lzy.coupon.apis.CouponServiceApi;
import com.lzy.coupon.dtos.CouponDto;
import com.lzy.framework.core.datasource.multiple.DataSource;
import com.lzy.framework.core.datasource.multiple.DataSourceHolder;
import com.lzy.framework.core.utils.DateUtil;
import com.lzy.framework.core.utils.StringUtil;
import com.lzy.framework.tools.commons.BigDecimalUtil;
import com.lzy.framework.tools.date.DateUtils;
import com.lzy.framework.tools.kv.KvClient;
import com.lzy.member.apis.MemberCouponServiceApi;
import com.lzy.member.apis.MemberIncrementServiceApi;
import com.lzy.member.apis.MemberUserServiceApi;
import com.lzy.member.dtos.MemberCouponDto;
import com.lzy.member.dtos.MemberIncrementDto;
import com.lzy.member.dtos.MemberUserDto;
import com.lzy.payment.apis.PayBillApi;
import com.lzy.payment.apis.PayMemberAccountApi;
import com.lzy.payment.dtos.memberAccount.PayMemberAccountDTO;
import com.lzy.payment.dtos.payBill.PayBillDTO;
import com.lzy.payment.dtos.queue.AgentSaleDTO;
import com.lzy.product.apis.*;
import com.lzy.product.constants.BusinessType;
import com.lzy.product.dtos.ProductUserDto;
import com.lzy.product.dtos.agent.*;
import com.lzy.product.dtos.profit.AgentProfitParamDto;
import org.slf4j.Logger;
import org.slf4j.LoggerFactory;
import org.springframework.beans.factory.annotation.Autowired;
import org.springframework.stereotype.Component;

import javax.annotation.Resource;
import java.math.BigDecimal;
import java.text.ParseException;
import java.text.SimpleDateFormat;
import java.util.Date;
import java.util.List;

import static com.lzy.framework.tools.date.DateStyle.YYYY_MM_DD;

/**
 * Created by WIN7 on 2018/4/17.
 */
@Component
public class AgentProfitFacade {

    private static final Logger LOGGER = LoggerFactory.getLogger(AgentProfitFacade.class);
    @Resource
    private KvClient kvClient;

    @Autowired
    PayBillApi payBillApi;

    @Autowired
    AgentProtocolServiceApi agentProtocolServiceApi;

    @Autowired
    CouponServiceApi couponServiceApi;

    @Autowired
    AgentProtocolCommissionServiceApi agentProtocolCommissionServiceApi;

    @Autowired
    AgentOrderYieldRatioServiceApi agentOrderYieldRatioServiceApi;

    @Autowired
    ProductUserServiceApi productUserServiceApi;

    @Autowired
    SysUserRoleServiceApi sysUserRoleServiceApi;

    @Autowired
    AgentPromoteServiceApi agentPromoteServiceApi;

    @Autowired
    AgentCommissionBillServiceApi agentCommissionBillServiceApi;

    @Autowired
    AgentOrderProjectRecordServiceApi agentOrderProjectRecordServiceApi;

    @Autowired
    AgentMemberProtocolServiceApi agentMemberProtocolServiceApi;

    @Autowired
    AgentProductProjectServiceApi agentProductProjectServiceApi;

    @Autowired
    MemberUserServiceApi memberUserServiceApi;

    @Autowired
    PayMemberAccountApi payMemberAccountApi;

    @Autowired
    AgentOrderInfoServiceApi agentOrderInfoServiceApi;

    @Autowired
    MemberBuyFacade memberBuyFacade;

    @Autowired
    MemberCouponServiceApi memberCouponServiceApi;

    @Autowired
    MemberIncrementServiceApi memberIncrementServiceApi;

    @Autowired
    AgentProductServiceApi agentProductServiceApi;

    /**
     * 计算各体系上级分利(协议)
     *
     * @param agentOrderInfoDto
     * @return
     */
    public Boolean calculateAgentProtocolProfit(AgentOrderInfoDto agentOrderInfoDto) {
        AgentProfitParamDto agentProfitParamDto = new AgentProfitParamDto();
        agentProfitParamDto.setOrderId(agentOrderInfoDto.getOrderId());
        agentProfitParamDto.setUserId(agentOrderInfoDto.getUserId());
        agentProfitParamDto.setSkuCode(agentOrderInfoDto.getSourceId());
        agentProfitParamDto.setOrderTime(agentOrderInfoDto.getPayTime());
        agentProfitParamDto.setOrderMoney(agentOrderInfoDto.getMoneyCount());
        String key = BusinessType.Cache.QUEUE_PRODUCT_PROFIT_RECORD + agentOrderInfoDto.getOrderId();
        String flag = kvClient.read(key, String.class);
        // 判断有没有执行过
        if (StringUtil.isNotBlank(flag) && BusinessType.Status.ONE.toString().equals(flag)) {
            // 订单已经分利，打印信息
            LOGGER.error("订单分利======失败======重复提交分利: " + JSON.toJSONString(agentOrderInfoDto));
            return false;
        }
        //给上级分利
        Boolean res = calculateAgentProtocol(agentProfitParamDto);
//        if (!res) {
//            // 订单分利失败，打印信息
//            LOGGER.error("订单分利失败：" + JSON.toJSONString(agentProfitParamDto));
//            return false;
//        }
        //更新收益比率
        Boolean ok = addOrderYieldRatio(agentProfitParamDto);
//        if (!ok) {
//            // 更新收益比率失败，打印信息
//            LOGGER.error("协议订单收益比率新增失败：" + JSON.toJSONString(agentProfitParamDto));
//            return false;
//        }
        kvClient.save(key, BusinessType.Status.ONE, BusinessType.EXPIRED_SECOND);
        return true;
    }

    /**
     * 计算分利(协议佣金)
     *
     * @param agentProfitParamDto
     * @return
     */
    public Boolean calculateAgentProtocol(AgentProfitParamDto agentProfitParamDto) {
        //订单ID必须传入
        if (agentProfitParamDto.getOrderId() == null) {
            LOGGER.error("协议订单佣金分利失败：orderId" + agentProfitParamDto.getOrderId());
            return false;
        }
        //判断该订单是否已经首销分利
        PayBillDTO payBillDTO = new PayBillDTO();
        payBillDTO.setSerialId(agentProfitParamDto.getOrderId());
        payBillDTO.setType(14);
        DataSourceHolder.setDataSource(DataSource.DATASOURCE_COMMON);
        List<PayBillDTO> payBillDTOList = payBillApi.selectList(payBillDTO);
        DataSourceHolder.clearDataSource();
        if (payBillDTOList.size() == 0) {
            //获取协议详情
            DataSourceHolder.setDataSource(DataSource.DATASOURCE_PRODUCT);
            AgentProtocolDto agentProtocolDto = agentProtocolServiceApi.selectDetailById(agentProfitParamDto.getSkuCode());
            if (agentProtocolDto == null) {
                LOGGER.error("协议详情数据未找到：orderId = " + agentProfitParamDto.getOrderId()
                        + ";protocolId = " + agentProfitParamDto.getSkuCode());
                return false;
            }
            //查看协议是否设置首次分佣
            AgentProtocolCommissionDto apcDto = new AgentProtocolCommissionDto();
            apcDto.setProtocolId(agentProfitParamDto.getSkuCode());
            apcDto.setType(1);
            List<AgentProtocolCommissionDto> apcDtoList = agentProtocolCommissionServiceApi.query(apcDto);
            //若apcDtoList为空，说明该协议没有首次分利。则不进行分利
            if (apcDtoList.size() == 0) {
                return true;
            } else {
                //首次销售分利
                //获取上级代理商列表
                List<ProductUserDto> idList = productUserServiceApi.selectListById(agentProfitParamDto.getUserId(), 1);
                if (idList != null && idList.size() > 0) {
                    //首销分利金额
                    BigDecimal profitComm = new BigDecimal(0);
                    return calculateProfit(2, idList, apcDtoList, agentProfitParamDto);
                }
            }
        }
        DataSourceHolder.clearDataSource();
        return true;
    }

    /**
     * 新增代理商
     */
    public Boolean updateAgentStatus(Long memberUserId) {
//        DataSourceHolder.setDataSource(DataSource.DATASOURCE_COMMON);
//        MemberUserDto memberUserDto = memberUserServiceApi.selectMemberByMemberId(MemberUserId);
//        DataSourceHolder.clearDataSource();
        ProductUserDto productUserDto = productUserServiceApi.findById(memberUserId);
//        sysUserRoleServiceApi

        if (productUserDto != null) {
//            ProductUserDto productUserDto = new ProductUserDto();
//            productUserDto.setPhone(memberUserDto.getAccount());
//            DataSourceHolder.setDataSource(DataSource.DATASOURCE_PRODUCT);
//            List<ProductUserDto> userDtoList = productUserServiceApi.query(productUserDto);
//            Ensure.that(userDtoList).isNotNull("01001606");
//            ProductUserDto pUdto = userDtoList.get(0);
            productUserDto.setState(0);
            //更新代理商状态
            Boolean flag = productUserServiceApi.update(productUserDto);
            if (flag) {
                //将用户绑定代理商角色
                SysUserRoleDto userRoleDto = new SysUserRoleDto();
                userRoleDto.setUserId(productUserDto.getId());
                userRoleDto.setRoleId(5L);
                return sysUserRoleServiceApi.addUserRole(userRoleDto);
            }
        }
        return false;
    }

    /**
     * 新增产品包含项
     *
     * @param type         （1-产品包含项 2-协议包含项）
     * @param agentSaleDTO
     * @return
     * @throws ParseException
     */
    public Boolean addProjects(Integer type, AgentSaleDTO agentSaleDTO) throws ParseException {
        AgentOrderInfoDto orderInfoDto = agentOrderInfoServiceApi.findByOrderId(Long.parseLong(agentSaleDTO.getOrderId()));
        if (orderInfoDto != null) {
            Long memberId = null;
            //代理商产品
            if (type == 1) {
                memberId = orderInfoDto.getMemberId();
                //添加会员与增值产品关联
                if(orderInfoDto.getSourceId() != null){
                    AgentProductDto agentProductDto = agentProductServiceApi.queryAgentProductById(orderInfoDto.getSourceId());
                    if(agentProductDto != null && agentProductDto.getCardId() != null) {
                        DataSourceHolder.setDataSource(DataSource.DATASOURCE_COMMON);
                        MemberIncrementDto memberIncrementDto = new MemberIncrementDto();
                        memberIncrementDto.setMemberId(memberId);
                        memberIncrementDto.setIncrementId(agentProductDto.getCardId());
                        List<MemberIncrementDto> memberIncrementDtoList = memberIncrementServiceApi.selectList(memberIncrementDto);
                        if(memberIncrementDtoList.size() == 0){
                            memberIncrementServiceApi.add(memberIncrementDto);
                        }
                        DataSourceHolder.clearDataSource();
                    }
                }
            }
            //代理商协议
            if (type == 2) {
                //获取2.1会员id
                ProductUserDto userDto = productUserServiceApi.findById(orderInfoDto.getMemberId());
                if (userDto != null && userDto.getPhone() != null) {
                    DataSourceHolder.setDataSource(DataSource.DATASOURCE_COMMON);
                    MemberUserDto memberUserDto = memberUserServiceApi.findMemberByMobile(userDto.getPhone());
                    DataSourceHolder.clearDataSource();
                    memberId = memberUserDto.getId();
                }
            }
            if (memberId != null) {
                List<AgentOrderProjectRecordDto> agentOrderProjectRecordDtoList = agentOrderProjectRecordServiceApi.selectAgentOrderProjectRecordByOrderId(Long.parseLong(agentSaleDTO.getOrderId()));
                if (agentOrderProjectRecordDtoList != null && agentOrderProjectRecordDtoList.size() > 0) {
                    for (AgentOrderProjectRecordDto aoprDto : agentOrderProjectRecordDtoList) {
                        if (aoprDto != null) {
                            switch (aoprDto.getProjectType()) {
                                case 1: //龙珠
                                    if (!addLzMemberAccount(orderInfoDto.getOrderId(), memberId, aoprDto.getCount())) {
                                        LOGGER.info("代理商协议支付成功新增龙珠失败：orderId=" + agentSaleDTO.getOrderId());
                                    }
                                    break;
                                case 3: //房车券
                                    if (!addCarCoupon(type, orderInfoDto.getSourceId(), memberId, aoprDto)) {
                                        LOGGER.info("代理商协议支付成功新增房车券失败：orderId=" + agentSaleDTO.getOrderId());
                                    }
                                    break;
                                case 4: //汽摩券
                                    if (!addMotorCoupon(type, orderInfoDto.getSourceId(), memberId, aoprDto)) {
                                        LOGGER.info("代理商协议支付成功新增汽摩券失败：orderId=" + agentSaleDTO.getOrderId());
                                    }
                                    break;
                                case 5: //代金券
                                    if (!addAgentCoupon(type, orderInfoDto.getSourceId(), memberId, aoprDto)) {
                                        LOGGER.info("代理商协议支付成功新增代金券失败：orderId=" + agentSaleDTO.getOrderId());
                                    }
                                    break;
                            }
                        }
                    }
                }
            }
        }
        return true;
    }

    /**
     * 新增龙珠
     *
     * @param orderId
     * @param memberId
     * @param number
     * @return
     */
    public Boolean addLzMemberAccount(Long orderId, Long memberId, Integer number) {
        DataSourceHolder.setDataSource(DataSource.DATASOURCE_COMMON);
        Boolean flag = payMemberAccountApi.updateLzMemberAccount(memberId, number);
        //添加龙珠充值记录
        if (flag) {
            PayBillDTO payBillDTO = new PayBillDTO();
            payBillDTO.setSerialId(orderId);
            payBillDTO.setUserId(memberId);
            payBillDTO.setType(1);
            payBillDTO.setAmount(new BigDecimal(number));
            payBillDTO.setDemo("龙珠充值");
            Boolean ok = payBillApi.createPayBill(payBillDTO);
            DataSourceHolder.clearDataSource();
            return ok;
        }
        DataSourceHolder.clearDataSource();
        return flag;
    }

    /**
     * 新增房车券
     *
     * @param type     1-产品包含项 2-协议包含项
     * @param serialId 产品id或协议id
     * @param memberId 会员id
     * @param aoprDto
     * @return
     */
    public Boolean addCarCoupon(Integer type, Long serialId, Long memberId, AgentOrderProjectRecordDto aoprDto) throws ParseException {
        AgentProductProjectDto productProjectDto = new AgentProductProjectDto();
        productProjectDto.setProjectId(aoprDto.getProjectId());
        productProjectDto.setSerialId(serialId);
        productProjectDto.setModel(type);
        List<AgentProductProjectDto> productProjectDtoList = agentProductProjectServiceApi.query(productProjectDto);
        if (productProjectDtoList != null && productProjectDtoList.size() > 0) {
            for (AgentProductProjectDto appDto : productProjectDtoList) {
                DataSourceHolder.setDataSource(DataSource.DATASOURCE_COMMON);
                CouponDto dto = memberBuyFacade.checkCouponBatchAndTypeCode("9699");
                dto.setType(2);
                dto.setCategory(1);
                dto.setChannel(3);
                dto.setRvType(BusinessType.CarCouponType.ALL_DAY_COUPON.getCode());
                dto.setValidTime(appDto.getValidTime());
                dto.setNumber(appDto.getContainNum());
                appDto = getTime(appDto);
                dto.setStartTime(appDto.getStartTime());
                dto.setExpiryTime(appDto.getExpiryTime());
                List<Long> ids = couponServiceApi.addCoupon(dto);
                MemberCouponDto memberCouponDto = new MemberCouponDto();
                memberCouponDto.setMemberId(memberId);
                memberCouponDto.setType(1);
                memberCouponDto.setCouponStatus(2);
                dto.setMode(BusinessType.CouponMode.GENERATION_TIME.getCode());
                memberCouponServiceApi.addMemberCoupon(dto, memberCouponDto);
                DataSourceHolder.clearDataSource();
            }
        }
        return true;
    }

    /**
     * 新增汽摩券
     *
     * @return
     */
    public Boolean addMotorCoupon(Integer type, Long serialId, Long memberId, AgentOrderProjectRecordDto aoprDto) throws ParseException {
        AgentProductProjectDto productProjectDto = new AgentProductProjectDto();
        productProjectDto.setProjectId(aoprDto.getProjectId());
        productProjectDto.setSerialId(serialId);
        productProjectDto.setModel(type);
        productProjectDto.setPrice(aoprDto.getPrice());
        List<AgentProductProjectDto> productProjectDtoList = agentProductProjectServiceApi.query(productProjectDto);
        if (productProjectDtoList != null && productProjectDtoList.size() > 0) {
            for (AgentProductProjectDto appDto : productProjectDtoList) {
                DataSourceHolder.setDataSource(DataSource.DATASOURCE_COMMON);
                CouponDto dto = memberBuyFacade.checkCouponBatchAndTypeCode("9699");
                dto.setType(2);
                dto.setCategory(3);
                dto.setChannel(3);
                dto.setRvType(BusinessType.CarCouponType.ALL_DAY_COUPON.getCode());
                dto.setValidTime(appDto.getValidTime());
                dto.setNumber(appDto.getContainNum());
                dto.setPrice(appDto.getPrice());
                appDto = getTime(appDto);
                dto.setStartTime(appDto.getStartTime());
                dto.setExpiryTime(appDto.getExpiryTime());
                List<Long> ids = couponServiceApi.addCoupon(dto);
                MemberCouponDto memberCouponDto = new MemberCouponDto();
                memberCouponDto.setMemberId(memberId);
                memberCouponDto.setType(3);
                memberCouponDto.setCouponStatus(2);
                dto.setMode(BusinessType.CouponMode.GENERATION_TIME.getCode());
                memberCouponServiceApi.addMemberCoupon(dto, memberCouponDto);
                DataSourceHolder.clearDataSource();
            }
        }
        return true;
    }

    /**
     * 新增房车代金券
     *
     * @param type     1-产品包含项 2-协议包含项
     * @param serialId 产品id或协议id
     * @param memberId 会员id
     * @param aoprDto
     * @return
     */
    public Boolean addAgentCoupon(Integer type, Long serialId, Long memberId, AgentOrderProjectRecordDto aoprDto) throws ParseException {
        AgentProductProjectDto productProjectDto = new AgentProductProjectDto();
        productProjectDto.setProjectId(aoprDto.getProjectId());
        productProjectDto.setSerialId(serialId);
        productProjectDto.setModel(type);
        List<AgentProductProjectDto> productProjectDtoList = agentProductProjectServiceApi.query(productProjectDto);
        if (productProjectDtoList != null && productProjectDtoList.size() > 0) {
            for (AgentProductProjectDto appDto : productProjectDtoList) {
                DataSourceHolder.setDataSource(DataSource.DATASOURCE_COMMON);
                CouponDto dto = memberBuyFacade.checkCouponBatchAndTypeCode("9699");
                dto.setType(2);
                dto.setCategory(1);
                dto.setChannel(3);
                dto.setRvType(BusinessType.CarCouponType.AGENT_MONEY_COUPON.getCode());
                dto.setValidTime(appDto.getValidTime());
                dto.setNumber(appDto.getContainNum());
                dto.setPrice(appDto.getPrice());
                appDto = getTime(appDto);
                dto.setStartTime(appDto.getStartTime());
                dto.setExpiryTime(appDto.getExpiryTime());
                List<Long> ids = couponServiceApi.addCoupon(dto);
                MemberCouponDto memberCouponDto = new MemberCouponDto();
                memberCouponDto.setMemberId(memberId);
                memberCouponDto.setType(1);
                memberCouponDto.setCouponStatus(2);
                dto.setMode(BusinessType.CouponMode.GENERATION_TIME.getCode());
                memberCouponServiceApi.addMemberCoupon(dto, memberCouponDto);
                DataSourceHolder.clearDataSource();
            }
        }
        return true;
    }

    /**
     * 计算开始时间和失效时间
     */
    public AgentProductProjectDto getTime(AgentProductProjectDto dto) {
//        DateUtil.compareDate()
        SimpleDateFormat df = new SimpleDateFormat("yyyy-MM-dd");//设置日期格式
        String currTime = df.format(new Date());
        Integer intervalDays;
        if (dto.getIntervalDays() == null) {
            intervalDays = 0;
        } else {
            intervalDays = dto.getIntervalDays();
        }
        //计算卡券的开始生效时间
        Date startDate = DateUtils.addDays(DateUtils.StringToDate(currTime, YYYY_MM_DD), intervalDays);
        String startTime = DateUtil.dateStr3(startDate);
        dto.setStartTime(startTime);
//        String startDay = df.format(startTime);
        //计算卡券的失效时间
        Date expiryDate = DateUtils.addDays(DateUtils.StringToDate(df.format(startDate), YYYY_MM_DD), dto.getValidTime());
        String expiryTime = DateUtil.dateStr3(expiryDate);
        dto.setExpiryTime(expiryTime);
        return dto;
    }

    /**
     * 计算各体系上级分利(产品)
     *
     * @param agentOrderInfoDto
     * @return
     */
    public Boolean calculateAgentProductProfit(AgentOrderInfoDto agentOrderInfoDto) {
        AgentProfitParamDto agentProfitParamDto = new AgentProfitParamDto();
        agentProfitParamDto.setOrderId(agentOrderInfoDto.getOrderId());
        agentProfitParamDto.setUserId(agentOrderInfoDto.getUserId());
        agentProfitParamDto.setSkuCode(agentOrderInfoDto.getSourceId());
        agentProfitParamDto.setOrderTime(agentOrderInfoDto.getPayTime());
        agentProfitParamDto.setOrderMoney(agentOrderInfoDto.getMoneyCount());
//        String key = BusinessType.Cache.QUEUE_PRODUCT_PROFIT_RECORD + agentOrderInfoDto.getOrderId();
//        String flag = kvClient.read(key, String.class);
//        // 判断有没有执行过
//        if (StringUtil.isNotBlank(flag) && BusinessType.Status.ONE.toString().equals(flag)) {
//            // 订单已经分利，打印信息
//            LOGGER.error("订单分利======失败======重复提交分利: " + JSON.toJSONString(agentOrderInfoDto));
//            return false;
//        }

        Boolean res = calculateAgentProduct(agentProfitParamDto);
        if (!res) {
            // 订单分利失败，打印信息
            LOGGER.error("订单分利失败：" + JSON.toJSONString(agentProfitParamDto));
            return false;
        }
//        kvClient.save(key, BusinessType.Status.ONE, BusinessType.EXPIRED_SECOND);
        return true;
    }

    /**
     * 计算分利(产品佣金)
     *
     * @param agentProfitParamDto
     * @return
     */
    public Boolean calculateAgentProduct(AgentProfitParamDto agentProfitParamDto) {
        //订单ID必须传入
        if (agentProfitParamDto.getOrderId() == null) {
            LOGGER.error("产品订单佣金分利失败：orderId" + agentProfitParamDto.getOrderId());
            return false;
        }
        //判断该订单是否已经销售分利
        PayBillDTO payBillDTO = new PayBillDTO();
        payBillDTO.setSerialId(agentProfitParamDto.getOrderId());
        payBillDTO.setType(19);
        DataSourceHolder.setDataSource(DataSource.DATASOURCE_COMMON);
        List<PayBillDTO> payBillDTOList = payBillApi.selectList(payBillDTO);
        DataSourceHolder.clearDataSource();
        //说明该订单木有进行销售分利
        if (payBillDTOList.size() == 0) {
            //获取协议详情
            if (agentProfitParamDto.getSkuCode() == null) {
                LOGGER.error("协议详情数据未找到：orderId = " + agentProfitParamDto.getOrderId()
                        + ";protocolId = " + agentProfitParamDto.getSkuCode());
                return false;
            }
            DataSourceHolder.setDataSource(DataSource.DATASOURCE_PRODUCT);
            //通过该会员查询出当时签的协议
            AgentMemberProtocolDto memberProtocolDto = new AgentMemberProtocolDto();
            memberProtocolDto.setMemberId(agentProfitParamDto.getUserId());
            List<AgentMemberProtocolDto> memberProtocolDtoList = agentMemberProtocolServiceApi.query(memberProtocolDto);
            //一个会员只会签署一份协议（一对一）
            if (memberProtocolDtoList != null && memberProtocolDtoList.size() > 0) {
                AgentMemberProtocolDto agentMemberProtocolDto = memberProtocolDtoList.get(0);
                if (agentMemberProtocolDto != null && agentMemberProtocolDto.getProtocolId() != null) {
                    //获取上级代理商列表
                    List<ProductUserDto> idList = productUserServiceApi.selectListById(agentProfitParamDto.getUserId(), 1);
                    if (idList != null && idList.size() > 0) {
                        //查询出该协议的销售分佣比例
                        AgentProtocolCommissionDto apcDto = new AgentProtocolCommissionDto();
                        apcDto.setProtocolId(agentMemberProtocolDto.getProtocolId());
                        apcDto.setType(2);
                        List<AgentProtocolCommissionDto> agentProtocolCommissionDtoList = agentProtocolCommissionServiceApi.query(apcDto);
                        if (agentProtocolCommissionDtoList != null && agentProtocolCommissionDtoList.size() > 0) {
                            AgentProtocolCommissionDto protocolCommissionDto = agentProtocolCommissionDtoList.get(0);
                            if (protocolCommissionDto != null && protocolCommissionDto.getPattern() != null) {
                                //固定模式
                                if (protocolCommissionDto.getPattern() == 1) {
                                    calculateProfit(1, idList, agentProtocolCommissionDtoList, agentProfitParamDto);
                                }
                                //升级模式
                                if (protocolCommissionDto.getPattern() == 2) {
                                    //获取该代理商累积销售额
                                    BigDecimal totalAmount = agentOrderInfoServiceApi.queryTotalPriceByUserId(agentProfitParamDto.getUserId());
                                    //根据订单金额获取分利等级
                                    AgentPromoteDto agentPromoteDto = agentPromoteServiceApi.queryByProtocolIdAndCriticalValue(agentMemberProtocolDto.getProtocolId(), totalAmount);
                                    if (agentPromoteDto != null && agentPromoteDto.getId() != null) {
                                        //根据条件查询出销售分佣比例
                                        AgentProtocolCommissionDto agentProtocolCommissionDto = new AgentProtocolCommissionDto();
                                        agentProtocolCommissionDto.setProtocolId(agentMemberProtocolDto.getProtocolId());
                                        agentProtocolCommissionDto.setPattern(2);
                                        agentProtocolCommissionDto.setType(2);
                                        agentProtocolCommissionDto.setPromoteId(agentPromoteDto.getId());
                                        List<AgentProtocolCommissionDto> protocolCommissionDtoList = agentProtocolCommissionServiceApi.query(agentProtocolCommissionDto);
                                        return calculateProfit(1, idList, protocolCommissionDtoList, agentProfitParamDto);
                                    }
                                }
                            }
                        }
                    }
                }
            }
            DataSourceHolder.clearDataSource();
        }
        return true;
    }

    //1-产品 2-协议
    public Boolean calculateProfit(Integer type, List<ProductUserDto> idList, List<AgentProtocolCommissionDto> protocolCommissionDtoList, AgentProfitParamDto agentProfitParamDto) {
        BigDecimal profitComm = new BigDecimal(0);
        for (AgentProtocolCommissionDto commissionDto : protocolCommissionDtoList) {
            if (commissionDto.getSystemId() != null) {
                //获取分利金额
                //百分比
                if (commissionDto.getMode() != null && commissionDto.getMode() == 1 && commissionDto.getValue() != null) {
                    //转换成小数
                    BigDecimal percent = commissionDto.getValue().divide(new BigDecimal(100));
                    profitComm = agentProfitParamDto.getOrderMoney().multiply(percent);
                } else if (commissionDto.getMode() != null && commissionDto.getMode() == 2 && commissionDto.getValue() != null) {
                    //元
                    profitComm = commissionDto.getValue();
                }
                //给上级分利
                addProfit(type, idList, commissionDto, profitComm, agentProfitParamDto);
            }
        }
        return true;
    }

    //对上级进行循环分利
    //1-产品 2-协议
    public Boolean addProfit(Integer type, List<ProductUserDto> idList, AgentProtocolCommissionDto commDto, BigDecimal profitComm, AgentProfitParamDto agentProfitParamDto) {
        for (ProductUserDto userDto : idList) {
            if (commDto.getSystemId() == userDto.getSystemId()) {
                DataSourceHolder.setDataSource(DataSource.DATASOURCE_COMMON);
                MemberUserDto memberUserDto = memberUserServiceApi.findMemberByMobile(userDto.getPhone());
                if (memberUserDto != null) {
                    //查询用户账户信息
                    PayMemberAccountDTO payAccount = new PayMemberAccountDTO();
                    payAccount.setUserId(memberUserDto.getId());
                    payAccount.setType(2);
                    payAccount.setRole(2);
                    payAccount.setStatus(0);
                    PayMemberAccountDTO memberAccountDTO = payMemberAccountApi.queryPayMemberAccount(payAccount);
                    if (memberAccountDTO == null) {
                        //无则新增
                        PayMemberAccountDTO memberAccountDTO1 = new PayMemberAccountDTO();
                        memberAccountDTO1.setUserId(memberUserDto.getId());
                        memberAccountDTO1.setType(2);
                        memberAccountDTO1.setRole(2);
                        memberAccountDTO1.setAmount(profitComm);
                        if (!payMemberAccountApi.addLbMemberAccount(memberAccountDTO1)) {
                            LOGGER.error("协议首销新增会员" + memberUserDto.getId() + "账户佣金余额" + profitComm + "元失败!");
                        }
                    } else {
                        //更新账户余额
                        PayMemberAccountDTO memberAccountDTO2 = new PayMemberAccountDTO();
                        memberAccountDTO2.setUserId(memberUserDto.getId());
                        memberAccountDTO2.setType(2);
                        memberAccountDTO2.setRole(2);
                        memberAccountDTO2.setAmount(memberAccountDTO.getAmount().add(profitComm));
                        if (!payMemberAccountApi.updatePayMemberAccount(memberAccountDTO2)) {
                            LOGGER.error("协议首销更新会员" + memberUserDto.getId() + "账户佣金余额" + memberAccountDTO2.getAmount() + "元失败!");
                        }
                    }
                    //添加资金记录
                    PayBillDTO payBillDto = new PayBillDTO();
                    if (type == 1) {
                        payBillDto.setType(19);
                        payBillDto.setDemo("产品销售分佣");
                    } else if (type == 2) {
                        payBillDto.setType(14);
                        payBillDto.setDemo("协议首销分佣");
                    }
                    payBillDto.setAmount(profitComm);
                    payBillDto.setCorrectFlag(0);
                    payBillDto.setUserId(memberUserDto.getId());
                    payBillDto.setSerialId(agentProfitParamDto.getOrderId());
                    if (!payBillApi.createPayBill(payBillDto)) {
                        LOGGER.error("产品销售分佣资金记录添加失败，订单号为" + agentProfitParamDto.getOrderId());
                    }
                    //添加佣金明细表详情记录 agent_commission_bill
                    AgentCommissionBillDto commissionBillDto = new AgentCommissionBillDto();
                    commissionBillDto.setMemberId(memberUserDto.getId());
                    commissionBillDto.setAmount(profitComm);
                    commissionBillDto.setOrderId(agentProfitParamDto.getOrderId());
                    commissionBillDto.setSourceId(agentProfitParamDto.getSkuCode());
                    if(type == 1){
                        commissionBillDto.setType(2);
                    }else if(type ==2){
                        commissionBillDto.setType(1);
                    }
                    if (memberUserDto.getName() != null) {
                        commissionBillDto.setName(memberUserDto.getName());
                    }
                    if (memberUserDto.getAccount() != null) {
                        commissionBillDto.setPhone(memberUserDto.getAccount());
                    }
                    DataSourceHolder.setDataSource(DataSource.DATASOURCE_PRODUCT);
                    agentCommissionBillServiceApi.insert(commissionBillDto);
                    DataSourceHolder.clearDataSource();
                }
                DataSourceHolder.clearDataSource();
            }
        }
        return true;
    }

    /**
     * 更新收益比率
     *
     * @param dto
     * @return
     */
    public Boolean addOrderYieldRatio(AgentProfitParamDto dto) {
        AgentOrderYieldRatioDto orderYieldRatioDto = new AgentOrderYieldRatioDto();
        orderYieldRatioDto.setOrderId(dto.getOrderId());
        List<AgentOrderYieldRatioDto> orderYieldRatioDtoList = agentOrderYieldRatioServiceApi.query(orderYieldRatioDto);
        if (orderYieldRatioDtoList != null && orderYieldRatioDtoList.size() > 0) {
            AgentOrderYieldRatioDto agentOrderYieldRatioDto = orderYieldRatioDtoList.get(0);
            if (agentOrderYieldRatioDto != null) {
                //从支付的第二天开始返现
                if (agentOrderYieldRatioDto.getCashbackTime() != null && !BigDecimalUtil.isZeroOrNull(agentOrderYieldRatioDto.getCashbackRatio())) {
                    SimpleDateFormat df = new SimpleDateFormat("yyyy-MM-dd");//设置日期格式
                    String currTime = df.format(new Date());
                    //计算返现开始日期
                    Date startTime = DateUtils.addDays(DateUtils.StringToDate(currTime, YYYY_MM_DD), 1);
                    String startDate = DateUtil.dateStr3(startTime).substring(0, 10);
                    agentOrderYieldRatioDto.setStartDate(startDate);
                    //计算返现截止日期
                    Date endTime = DateUtils.addDays(DateUtils.StringToDate(df.format(startTime), YYYY_MM_DD), agentOrderYieldRatioDto.getCashbackTime() + 1);
                    String endDate = DateUtil.dateStr3(endTime).substring(0, 10);
                    agentOrderYieldRatioDto.setEndDate(endDate);
                    //计算日收益
                    if (!BigDecimalUtil.isZeroOrNull(agentOrderYieldRatioDto.getPrice())) {
                        BigDecimal percent = agentOrderYieldRatioDto.getCashbackRatio().divide(new BigDecimal(100));
                        if (!BigDecimalUtil.isZeroOrNull(percent)) {
                            //总收益
                            BigDecimal totalAmount = agentOrderYieldRatioDto.getPrice().multiply(percent);
                            //日收益
                            BigDecimal dailyIncome = totalAmount.divide(new BigDecimal(agentOrderYieldRatioDto.getCashbackTime()), 2, BigDecimal.ROUND_HALF_DOWN);
                            agentOrderYieldRatioDto.setDailyIncome(dailyIncome);
                        }
                    }
                    return agentOrderYieldRatioServiceApi.update(agentOrderYieldRatioDto);
                }
            }
        }
        return false;
    }

}
